import 'dart:convert';
import 'dart:math';
import 'package:suxuanapp/utils/extend.dart';
import 'package:dio/dio.dart';
import 'package:suxuanapp/http/http_router.dart';
import 'dart:async';
import 'package:suxuanapp/web/js_bridge.dart';

const Target_IP_Port = "Target_IP_Port"; //代理相应错误
var tmp ={
  "Accept":
  "application/json,application/xml,application/xhtml+xml,text/html;q=0.9,image/webp,*/*;q=0.8"
  ,
  "Accept-Encoding":
  "gzip, deflate"
  ,
  "Accept-Language":
  "zh-CN,zh"
  ,
  "Access-Token":
  "FF32C43E46932F400BA5578777939E4A"
  ,
  "Connection":
  "keep-alive"
  ,
  "Content-Length":
  "19"
  ,
  "Content-Type":
  "application/x-www-form-urlencoded; charset=utf-8"
  ,
  "Content-Typeflag":
  "application/json"
  ,
  "Cookie":
  "PHPSESSID=r9tn11doie56blgo82a08jc9t0"
  ,
  "Nonce":
  "903872"
  ,
  "Signature":
  "4f192747eda16f776a95846c0f0f1e4f"
  ,
  "Timestamp":
  "1599725437"
  ,
  "Target_IP_Port":"http://auth.suxuantech.cn",
  "User-Agent":
  "Mozilla/5.0 (Linux; U; Android 10; zh-cn; Redmi K20 Pro Premium Edition Build/QKQ1.190825.002) AppleWebKit/533.1 (KHTML, like Gecko) Version/5.0 Mobile Safari/533.1"

};
class DioUtil {
  static Dio _dio = new Dio();
  //在 Dart 里，带下划线开头的变量是私有变量
  static DioUtil _instance;
  static DioUtil getInstance() {
    if (_instance == null) {
      _instance = DioUtil();
    }
    return _instance;
  }

  post(url, Function successCallBack,
      {data,
        headers,
        Map<String, String> queryParameters,
        Options options,
        CancelToken cancelToken,
        ProgressCallback onSendProgress,
        ProgressCallback onReceiveProgress,
        Function errorCallBack,
        useProxy = true}) async {
    if (options == null) {
      options = Options();
    }
    options.method = "POST";
    request(url, successCallBack,
        data: data,
        headers: headers,
        queryParameters: queryParameters,
        options: options,
        cancelToken: cancelToken,
        onSendProgress: onSendProgress,
        onReceiveProgress: onReceiveProgress,
        errorCallBack: errorCallBack,
        useProxy: useProxy);
  }

  /**
   * url 请求地址
   * successCallBack 请求成功的回调
   * queryParameters url 参数
   *data 体参数或者json等
   * options 配置
   * cancelToken
   * onSendProgress 发送进度
   * onReceiveProgress   接受进度
   * errorCallBack 错误回调
   * useProxy 是否启用代理
   */
  request(url, Function successCallBack,
      {headers,
        Map<String, String> queryParameters,
        data,
        Options options,
        CancelToken cancelToken,
        ProgressCallback onSendProgress,
        ProgressCallback onReceiveProgress,
        Function errorCallBack,
        useProxy = true}) async {
    Response response;
    var uri = Uri.parse(url);
    if (options == null) {
      options = Options();
    }
    if (runOnH5 && useProxy) {
      var uritmp = Uri.parse(HttpRouter.porxyIPPort);
      options.headers.addAll({
        Target_IP_Port:
        uri.scheme + "://" + uri.host + ":" + uri.port.toString()
      });
      //目标地址IP端口号
      //转换成uri
      //请求地址修改
      var proxyRequestUri =  uri.replace(scheme: uri.scheme, host: uritmp.host, port: uritmp.port);
      uri = proxyRequestUri;
      print("代理请求地址");
      print(uri);
    }
    if (headers != null) {
      options.headers.addAll(headers);
    }
//    options.headers.clear();
//    options.headers.addAll(tmp);
    var signature = getSignature();
    options.headers.addAll(signature);
//    options. headers=tmp;
    try {
      response = await _dio.post(uri.toString(),    data: data, options: options, queryParameters: queryParameters);
    } on DioError catch (error, s) {
// 请求错误处理
      Response errorResponse;
      if (error.response != null) {
        errorResponse = error.response;
      } else {
        errorResponse = new Response(statusCode: 666);
      }
      errorCallBack(errorResponse);
      return;
    }

//    String dataStr = json.encode(response.data);
    var responsData =   response.data;
    try{
      //解析成JOS对象
      Map<String, dynamic> dataMap = json.decode(responsData);
      successCallBack(dataMap);
    }catch(e){
      //json 对象解析失败则尝试解析jsons数组
      try{
        List responseJson = json.decode(responsData);
        successCallBack(responseJson);
      }catch(e){
        //数组解析失败，则认为返回的是字符串，直接返回
        successCallBack(responsData);
      }
    }
  }


  /***
   * 签名
   */
  getSignature() {
    String signature = "oUWKYeqCEojOvbmsynvWTctJSAVeoMZv";
    int Min = 99999;
    int Max = 999999;
    var rng = new Random();
    int random = Min + rng.nextInt(Max - Min);
    //时间戳是13位的毫秒,1000毫秒=1秒,所以需要除以一千 得到的是秒的时间戳也就是10位的
    var currentTimeMillis =
    (new DateTime.now().millisecondsSinceEpoch / 1000).toInt();
    var tmp = "$currentTimeMillis$random$signature";
    var a = {
      "currentTimeMillis": currentTimeMillis,
      "random": random,
      "signature": tmp.toMd5()
    };
    return a;
  }

  //拦截器部分
  tokenInter() {
    _dio.interceptors
        .add(InterceptorsWrapper(onRequest: (RequestOptions options) {
      // 在发送请求之前做一些预处理
      //我这边是在发送前到SharedPreferences（本地存储）中取出token的值，然后添加到请求头中
      //dio.lock()是先锁定请求不发送出去，当整个取值添加到请求头后再dio.unlock()解锁发送出去
      _dio.lock();
      Future<dynamic> future = Future(() async {
//            SharedPreferences prefs =await SharedPreferences.getInstance();
//            return prefs.getString("loginToken");
      });

      return future.then((value) {
        options.headers["Authorization"] = value;
        return options;
      }).whenComplete(() => _dio.unlock()); // unlock the dio
    }, onResponse: (Response response) {
      // 在返回响应数据之前做一些预处理
      return response; // continue
    }, onError: (DioError e) {
      // 当请求失败时做一些预处理
      return e; //continue
    }));
  }
}
